home *** CD-ROM | disk | FTP | other *** search
- /* SND */
- /* IMPORT/EXPORT */
- /* v 1.0 */
- /* 1996 by ANR */
-
- // Usage:
-
- #include "PPPlug.h"
- #include "sound.h"
- #include "soundinput.h"
-
- Ptr MyExp1to3( Ptr sound, unsigned long numSampleFrames);
- Ptr MyExp1to6( Ptr sound, unsigned long numSampleFrames);
-
- #if defined(powerc) || defined(__powerc)
- enum {
- PlayerPROPlug = kCStackBased
- | RESULT_SIZE(SIZE_CODE( sizeof(OSErr)))
- | STACK_ROUTINE_PARAMETER(1, SIZE_CODE(sizeof( OSType)))
- | STACK_ROUTINE_PARAMETER(2, SIZE_CODE(sizeof( InstrData*)))
- | STACK_ROUTINE_PARAMETER(3, SIZE_CODE(sizeof( sData**)))
- | STACK_ROUTINE_PARAMETER(4, SIZE_CODE(sizeof( short*)))
- | STACK_ROUTINE_PARAMETER(5, SIZE_CODE(sizeof( FSSpec*)))
- | STACK_ROUTINE_PARAMETER(6, SIZE_CODE(sizeof( PPInfoPlug*)))
- };
-
- ProcInfoType __procinfo = PlayerPROPlug;
- #else
- #include <A4Stuff.h>
- #endif
-
-
- void AddLoopToSndHandle( Handle sound, long Start, long End)
- {
- Ptr soundPtr;
- short soundFormat;
- short numSynths, numCmds;
- long offset;
- SoundHeaderPtr header;
- CmpSoundHeader *CmpHeader;
- ExtSoundHeader *ExtHeader;
- OSErr result;
-
- // make the sound safe to use at interrupt time.
- HLock( sound);
- soundPtr = *sound;
-
- // determine what format sound we have.
- soundFormat = *(short*)soundPtr;
-
- switch(soundFormat)
- {
- case 1: // format 1 sound.
- // look inside the format 1 resource and deduce offsets.
- numSynths = ((short*)soundPtr)[1]; // get # synths.
- numCmds = *(short*)(soundPtr+4+numSynths*6); // get # commands.
- break;
-
- case 2: // format 2 sound.
- numSynths = 0; // format 2 sounds have no synth's.
- numCmds = ((short*)soundPtr)[2];
- break;
-
- default: // jack says, what about 12? or 6?
- DebugStr("\p NSndToHandle... Burkk");
- }
-
- // compute address of sound header.
- offset = 6 + 6*numSynths + 8*numCmds;
- header = (SoundHeaderPtr) (StripAddress(*sound) + offset);
-
- switch( header->encode)
- {
- case cmpSH:
- CmpHeader = (CmpSoundHeader*) header;
- if( CmpHeader->sampleSize == 16) { Start /= 2; End /= 2; }
-
- CmpHeader->loopStart = Start;
- CmpHeader->loopEnd = End;
- break;
-
- case extSH:
- ExtHeader = (ExtSoundHeader*) header;
- if( ExtHeader->sampleSize == 16) { Start /= 2; End /= 2; }
-
- ExtHeader->loopStart = Start;
- ExtHeader->loopEnd = End;
- break;
-
- case stdSH:
- header->loopStart = Start;
- header->loopEnd = End;
- break;
- }
-
- HUnlock( sound);
- }
-
- Ptr SndToPtr( Ptr soundPtr, long *loopStart, long *loopEnd, short *sampleSize, unsigned long *sampleRate, long *baseFreq)
- {
- short soundFormat, numChannels;
- short numSynths, numCmds, CompressID;
- long offset, MusSize;
- SoundHeaderPtr header;
- CmpSoundHeader *CmpHeader;
- ExtSoundHeader *ExtHeader;
- SndCommand cmd;
- OSErr result;
- long i,x, numFrames;
- Boolean change = false;
- Str255 aStr;
-
- *loopStart = 0;
- *loopEnd = 0;
- *sampleSize = 8;
-
- // determine what format sound we have.
- soundFormat = *(short*) soundPtr;
-
- switch( soundFormat)
- {
- case 1: // format 1 sound.
- // look inside the format 1 resource and deduce offsets.
- numSynths = ((short*)soundPtr)[1]; // get # synths.
- numCmds = *(short*)(soundPtr+4+numSynths*6); // get # commands.
- break;
-
- case 2: // format 2 sound.
- numSynths = 0; // format 2 sounds have no synth's.
- numCmds = ((short*)soundPtr)[2];
- break;
-
- default: // jack says, what about 12? or 6?
- DebugStr("\p NSndToHandle... Burkk");
- break;
- }
-
- // compute address of sound header.
- offset = 6 + 6*numSynths + 8*numCmds;
- header = (SoundHeaderPtr) ( ((Ptr) soundPtr) + offset);
-
- switch( header->encode)
- {
- case cmpSH:
- CmpHeader = (CmpSoundHeader*) header;
- CompressID = CmpHeader->compressionID;
- numChannels = CmpHeader->numChannels;
-
- *loopStart = CmpHeader->loopStart;
- *loopEnd = CmpHeader->loopEnd;
- *sampleSize = CmpHeader->sampleSize;
-
- if( sampleRate != 0L) *sampleRate = CmpHeader->sampleRate;
- if( baseFreq != 0L) *baseFreq = CmpHeader->baseFrequency;
-
- MusSize = (*CmpHeader).numFrames;
-
- BlockMove( (*CmpHeader).sampleArea, soundPtr, MusSize);
-
- switch( CompressID )
- {
- case threeToOne:
- MusSize *= 2;
- soundPtr = MyExp1to3( soundPtr, MusSize);
- MusSize *= 3;
- break;
-
- case sixToOne:
- soundPtr = MyExp1to6( soundPtr, MusSize);
- MusSize *= 6;
- break;
-
- default:
- return 0L;
- break;
- }
-
- break;
-
- case extSH:
- ExtHeader = (ExtSoundHeader*) header;
-
- MusSize = ExtHeader->numFrames;
- numChannels = ExtHeader->numChannels;
-
- *loopStart = ExtHeader->loopStart;
- *loopEnd = ExtHeader->loopEnd;
- *sampleSize = ExtHeader->sampleSize;
-
- if( sampleRate != 0L) *sampleRate = ExtHeader->sampleRate;
- if( baseFreq != 0L) *baseFreq = ExtHeader->baseFrequency;
-
- if( *sampleSize == 16)
- {
- MusSize *= 2;
- *loopStart *= 2;
- *loopEnd *= 2;
- }
-
- if( numChannels == 1) BlockMove( ExtHeader->sampleArea, soundPtr, MusSize);
- else
- {
- if( *sampleSize == 8)
- {
- for( i = 0; i < MusSize; i ++)
- {
- soundPtr[ i] = ExtHeader->sampleArea[ i * numChannels];
- }
- }
- else
- {
- MusSize /= 2;
- for( i = 0; i < MusSize; i ++)
- {
- ((short*) soundPtr)[ i] = ((short*) ExtHeader->sampleArea)[ i * numChannels];
- }
- MusSize *= 2;
- }
- }
- break;
-
- default:
- case stdSH:
- *loopStart = header->loopStart;
- *loopEnd = header->loopEnd;
-
- if( sampleRate != 0L) *sampleRate = header->sampleRate;
- if( baseFreq != 0L) *baseFreq = header->baseFrequency;
-
- MusSize = header->length;
- BlockMove( (*header).sampleArea, soundPtr, MusSize);
- break;
- }
- SetPtrSize( soundPtr, MusSize);
- if( MemError() != noErr) Debugger();
-
- if( *sampleSize == 8) ConvertInstrumentIn( (Byte*) soundPtr, MusSize);
-
- if( *loopEnd - *loopStart < 4) { *loopEnd = 0; *loopStart = 0;}
-
- return soundPtr;
- }
-
-
- OSErr TestSND( short *soundPtr)
- {
- if( *soundPtr == 1 || *soundPtr == 2) return noErr;
- else return MADFileNotSupportedByThisPlug;
- }
-
- Ptr IMPL( long *lS, long *lE, long *bFreq, short *sS, unsigned long *rate, FSSpec *AlienFileFSSpec)
- {
- Handle tempHandle;
- Ptr theSound = 0L;
- short iFileRefI;
- OSErr myErr = noErr;
-
- iFileRefI = FSpOpenResFile( AlienFileFSSpec, fsCurPerm);
-
- if( ResError())
- {
- CloseResFile( iFileRefI); myErr = ResError(); goto End;
- }
-
- UseResFile( iFileRefI);
-
- if( Count1Resources( 'snd ') == 0)
- {
- CloseResFile( iFileRefI); myErr = ResError(); goto End;
- }
-
- tempHandle = Get1IndResource('snd ', 1);
- if( tempHandle != 0L)
- {
- DetachResource( tempHandle);
-
- theSound = NewPtr( GetHandleSize( tempHandle));
- if( theSound != 0L)
- {
- HLock( tempHandle);
- BlockMove( *tempHandle, theSound, GetHandleSize( tempHandle));
- HUnlock( tempHandle);
-
- theSound = SndToPtr( theSound, lS, lE, sS, rate, bFreq);
-
- if( theSound == 0L)
- {
- DisposeHandle( tempHandle);
- CloseResFile( iFileRefI);
- myErr = MADNeedMemory;
- goto End;
- }
- }
- else
- {
- DisposeHandle( tempHandle);
- CloseResFile( iFileRefI);
- myErr = MADNeedMemory;
- goto End;
- }
-
- DisposeHandle( tempHandle);
- tempHandle = 0L;
- }
- else
- {
- CloseResFile( iFileRefI);
- myErr = MADNeedMemory;
- goto End;
- }
- CloseResFile( iFileRefI);
-
- End:;
-
- if( myErr != noErr) return 0L;
- else return theSound;
- }
-
- OSErr main( OSType order, // Order to execute
- InstrData *InsHeader, // Ptr on instrument header
- sData **sample, // Ptr on samples data
- short *sampleID, // If you need to replace/add only a sample, not replace the entire instrument (by example for 'AIFF' sound)
- // If sampleID == -1 : add sample else replace selected sample.
- FSSpec *AlienFileFSSpec, // IN/OUT file
- PPInfoPlug *thePPInfoPlug)
- {
- OSErr myErr = noErr;
- Ptr AlienFile;
- short iFileRefI;
- long inOutBytes;
-
- #ifndef powerc
- long oldA4 = SetCurrentA4(); //this call is necessary for strings in 68k code resources
- #endif
-
- switch( order)
- {
- case 'PLAY':
- {
- long lS, lE, bFreq;
- short sS;
- unsigned long rate;
- Ptr theSound;
-
- theSound = IMPL( &lS, &lE, &bFreq, &sS, &rate, AlienFileFSSpec);
-
- if( theSound != 0L)
- {
- myErr = CallRPlaySoundUPP( theSound, GetPtrSize( theSound), 0, 0xFF, sS, lS, lE, rate);
-
- DisposePtr( theSound);
- theSound = 0L;
- }
- }
- break;
-
- case 'IMPL':
- {
- long lS, lE, bFreq;
- short sS;
- unsigned long rate;
- Ptr theSound;
-
- theSound = IMPL( &lS, &lE, &bFreq, &sS, &rate, AlienFileFSSpec);
-
- if( theSound != 0L)
- {
- AddSoundToMAD( theSound, lS, lE, sS, bFreq, rate, AlienFileFSSpec->name, InsHeader, sample, sampleID);
- myErr = noErr;
- }
- else myErr = MADNeedMemory;
- }
- break;
-
- case 'TEST':
- myErr = noErr;
-
- iFileRefI = FSpOpenResFile( AlienFileFSSpec, fsCurPerm);
-
- if( ResError())
- {
- CloseResFile( iFileRefI); myErr = ResError(); goto End;
- }
-
- UseResFile( iFileRefI);
-
- if( Count1Resources( 'snd ') == 0) myErr = MADFileNotSupportedByThisPlug;
-
- CloseResFile( iFileRefI);
- break;
-
- case 'EXPL':
- if( *sampleID >= 0)
- {
- sData *curData = sample[ *sampleID];
- short temp, fRefNum;
- Handle tempHandle;
-
- tempHandle = NewHandle( 2048L);
-
- inOutBytes = curData->size;
-
- SetupSndHeader( (SndListHandle) tempHandle,
- 1,
- ((unsigned long) curData->c2spd)<<16L,
- curData->amp,
- 'NONE',
- 60 - curData->relNote,
- inOutBytes,
- &temp);
-
- SetHandleSize( tempHandle, inOutBytes + temp);
-
- HLock( tempHandle);
- BlockMove( curData->data, *tempHandle + temp, inOutBytes);
-
- if( curData->amp == 8) ConvertInstrumentIn( (Byte*) *tempHandle + temp, inOutBytes);
-
- HUnlock( tempHandle);
-
- AddLoopToSndHandle( tempHandle,
- curData->loopBeg,
- curData->loopBeg + curData->loopSize);
-
- FSpDelete( AlienFileFSSpec);
- FSpCreateResFile( AlienFileFSSpec, 'movr', 'sfil', smCurrentScript);
- fRefNum = FSpOpenResFile( AlienFileFSSpec, fsCurPerm);
- UseResFile( fRefNum);
- AddResource( tempHandle, 'snd ', 7438, AlienFileFSSpec->name);
- WriteResource( tempHandle);
- DetachResource( tempHandle);
-
- DisposeHandle( tempHandle);
-
- CloseResFile( fRefNum);
- }
- break;
-
- default:
- myErr = MADOrderNotImplemented;
- break;
- }
-
- End:
-
- #ifndef powerc
- SetA4( oldA4);
- #endif
-
- return myErr;
- }